/* COPYRIGHT_CHUNFENG */
#include <unistd.h>
#include <sys/select.h>
#include <signal.h>
#include <stdarg.h>
#include <errno.h>
#include "cf_std.h"
#include "cf_sigfd.h"

static int signal_pipe[2];
void _signal_handler(int sig)
{
    write(signal_pipe[1], &sig, sizeof(sig));
}

int cf_sigfd_open(int s, ...)
{
    va_list ap;
    int sig;
    
    if(pipe(signal_pipe) == -1){
        return -1;
    }
    va_start(ap, s);
    sig = s;
    while(sig>0){
        signal(sig, _signal_handler);
        sig = va_arg(ap, int);
    }
    va_end(ap);
    return signal_pipe[0];
}

void cf_sigfd_close()
{
    close(signal_pipe[0]);
    close(signal_pipe[1]);
}

int cf_sigfd_get_next_signal(int fd)
{
    int sig;
    read(fd, &sig, sizeof(sig));
    return sig;
}

#if 0
int main(int argc)
{
    int sigfd, res;
    fd_set fds;    
    sigfd = cf_sigfd_open(SIGHUP, SIGUSR1, SIGINT, 0);
    if(sigfd == -1){
        return -1;
    }
    while(1){
        FD_ZERO(&fds);
        FD_SET(sigfd, &fds);
        printf("before select\n");
        if(-1 == select(sigfd+1, &fds, NULL, NULL, NULL)){
            if(errno == EINTR){
                printf("Interrput caused the select exit, We will handle it with cf_sigfd!!\n");
            }else{
                    res = -1;
                    goto OUT0;
            }
        }
        if(FD_ISSET(sigfd, &fds)){
            int exit = 0;
            switch(cf_sigfd_get_next_signal(sigfd)){
                case SIGUSR1:
                    printf("Got SIGUSR1\n");
                    break;
                case SIGHUP:
                    printf("Got SIGHUP\n");
                    break;
                case SIGINT:
                    printf("Bye Bye\n");
                    exit = 1;
                    break;
                default:
                    printf("Unknown signal\n");
            }
            if(exit){
                res = 0;
                goto OUT0;
            }
        }
    }
    
OUT0:
    cf_sigfd_close();
    return res;
}
#endif
